<template>
  <div class="table-layout">
    <div class="table-header" ref="tableHeaderRef">
      <a-space class="table-header-space" wrap>
        <template :key="index" v-for="(item, index) in tableHeader().left">
          <slot :name="item.name" :record="item" :rowIndex="index">
            <component
              :is="item.render"
              v-if="item.type === 'render' && item.render"
            ></component>
            <a-button
              :disabled="item.disabled"
              @click="onTableHeaderClick(item)"
              type="primary"
              v-else
            >
              <template #icon>
                <component :is="item.icon"></component>
              </template>
              <template #default v-if="item.label">{{ item.label }}</template>
            </a-button>
          </slot>
        </template>
      </a-space>
      <a-space class="table-header-space" wrap>
        <template :key="index" v-for="(item, index) in tableHeader().right">
          <slot :name="item.name" :record="item" :rowIndex="index">
            <component
              :is="item.render"
              v-if="item.type === 'render' && item.render"
            ></component>
            <a-button
              :disabled="item.disabled"
              @click="onTableHeaderClick(item)"
              type="primary"
              v-else
            >
              <template #icon>
                <component :is="item.icon"></component>
              </template>
              <template #default v-if="item.label">{{ item.label }}</template>
            </a-button>
          </slot>
        </template>
      </a-space>
    </div>
    <component
      :is="Render()"
      @page-change="onPageChange"
      @page-size-change="onPageSizeChange"
      @select="handleRowClick"
      id="my-table"
      v-bind="{
        ...$attrs,
        ...tableConfig(),
      }"
    ></component>
  </div>
</template>

<script setup lang="tsx">
import { computed, ref } from "vue";
import { Table, Empty } from "@arco-design/web-vue";
import type { TableProps, TableHeader } from "./type";
const slots = defineSlots();
const emit = defineEmits([
  "headerClick",
  "update:current",
  "update:pageSize",
  "pageChange",
  "pageSizeChange",
  "handleRowClick",
]);
const props = withDefaults(defineProps<TableProps>(), {
  tableHeader: () => [],
  columns: () => [],
  data: () => [],
  scrollbar: true,
  scroll: () => ({
    x: "100%",
    y: "100%",
  }),
  rowSelection: () => ({
    type: "checkbox",
  }),
  stripe: true,
  border: false,
  rowKey: "id",

  subtractHeight: 210,
  total: 50,
  pageSize: 20,
  current: 1,
  pagination: () => ({
    showTotal: true,
    showJumper: true,
    showPageSize: true,
    hideOnSinglePage: true,
  }),
});

//#region 头部设置
const tableHeaderRef = ref<HTMLDivElement>();
const tableHeader = () => {
  let tableHeaders: TableHeader[] = [
    ...props.tableHeader,
    {
      name: "refresh",
      type: "button",
      align: "right",
      icon: "icon-refresh",
      key: 100,
    },
  ];
  return {
    left: tableHeaders.filter((item) => item.align != "right") || [],
    right: tableHeaders.filter((item) => item.align === "right") || [],
  };
};

const handleRowClick = (row: []) => {
  emit("handleRowClick", row);
};
const onTableHeaderClick = (data: TableHeader) => {
  emit("headerClick", data);
};
//#endregion
//#region 分页

const pageSize = computed({
  get() {
    return props.pageSize;
  },
  set(val) {
    emit("update:pageSize", val);
  },
});
const current = computed({
  get() {
    return props.current;
  },
  set(val) {
    emit("update:current", val);
  },
});
const onPageChange = (page: number) => {
  current.value = page;
  emit("pageChange", page);
};
const onPageSizeChange = (page_size: number) => {
  pageSize.value = page_size;
  emit("pageSizeChange", page_size);
};
//#endregion
//#region 表格配置
const tableConfig = () => {
  let config = props;
  let collocate = {
    ...config,
  };
  if (config.rowSelection) {
    if (config.rowSelection.type === "radio") {
      config.rowSelection.showCheckedAll = false;
    }
    collocate.rowSelection = {
      ...config.rowSelection,
      onlyCurrent: true,
    };
  } else {
    collocate.rowSelection = null;
  }

  return {
    ...collocate,
    pagination: {
      ...config.pagination,
      total: config.total,
      pageSize: pageSize.value,
      current: current.value,
    },
  };
};
//#endregion
// 减去高度
const tableHeaderHeight = ref<any>(0);
const subtractHeight = computed(() => {
  if (props.height) {
    return typeof props.height === "number"
      ? `${props.height}px`
      : props.height;
  }

  const headerHeight =
    tableHeaderHeight.value || tableHeaderRef.value?.offsetHeight;

  let tableHeight = props.subtractHeight + (headerHeight || 0);
  return `100vh - ${tableHeight}px`;
});
window.addEventListener("resize", () => {
  tableHeaderHeight.value = tableHeaderRef.value?.offsetHeight;
});

const Render = () => {
  return (
    <Table>
      {{
        ...slots,
        empty: () => (
          <>
            <div class="table-empty">
              <Empty />
            </div>
          </>
        ),
      }}
    </Table>
  );
};
</script>

<style lang="scss" scoped>
.table-layout {
  --table-heaght: calc(v-bind(subtractHeight));
  margin: 20px;
  overflow: hidden;
  background-color: #fff;
  box-sizing: border-box;

  .table-header {
    min-height: 30px;
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    box-sizing: border-box;

    .table-header-space {
      margin-bottom: 10px;
    }
  }

  :deep(
      #my-table
        .arco-table-container
        .arco-scrollbar
        .arco-scrollbar-container
        .arco-scrollbar-type-embed
        .arco-table-body
    ) {
    height: var(--table-heaght);
  }

  .table-empty {
    height: var(--table-heaght);
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 20px;
    color: #999;
  }
}
</style>
